﻿#region Imports
using System;
using System.ComponentModel;
using System.Diagnostics;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Media.Imaging;
using System.Windows.Threading;
using CommonUtilities.Extensions;
using CommonUtilities.Messages;
using EntertainmentManager.ViewModels;
#endregion

namespace EntertainmentManager.Views
{
    /// <summary>
    /// Interaction logic for frmEntertainmentManager.xaml
    /// </summary>
    public partial class frmEntertainmentManager : Window
    {
        MainViewModel dataContext;

        public frmEntertainmentManager()
        {
            try
            {
                InitializeComponent();

                MessageBoxUtil.Show(true, "http://www.codeproject.com/Articles/43525/WPF-DataGrid-Using-DataTemplates-for-auto-generate");
                Dispatcher.CurrentDispatcher.BeginInvoke(new Action(() =>
                {
                    dataContext = new MainViewModel();
                    this.Loaded += (s, e) => { this.DataContext = dataContext; };
                }));
            }
            catch (Exception ex)
            {
                MessageBoxUtil.Show(Debugger.IsAttached, ex.StackTrace, ex.Message);
            }

            return;
            //Dispatcher.CurrentDispatcher.BeginInvoke(new Action(() =>
            //{
            //    // http://stackoverflow.com/questions/569561/dynamic-loading-of-images-in-wpf
            //    string url = "http://www.codeproject.com/images/OpenWithWS.gif";
            //    BitmapImage bitmap = new BitmapImage();
            //
            //    bitmap.BeginInit();
            //    bitmap.UriSource = new Uri(url, UriKind.Absolute);
            //    bitmap.CacheOption = BitmapCacheOption.OnLoad;
            //    bitmap.EndInit();
            //
            //    new Imagine(bitmap).ShowDialog();
            //    // Application.Current.Shutdown();
            //}));
        }

        private void dgrdUniversal_AutoGeneratingColumn(object sender, DataGridAutoGeneratingColumnEventArgs e)
        {
            // RKD - new attrib
            //e.Column.ColumnType = ColumnTypeAttribute;
            //e.Column.ValueType = DataTypeAttribute;

            string propName = e.PropertyName;

            e.Cancel = !dataContext.validHeaders.Contains(propName);
            if (e.Cancel) return;

            // Column styling
            e.Column = UpdateColumnStyle(e.Column, propName);
        }

        private void dgrdUniversal_AutoGeneratedColumns(object sender, EventArgs e)
        {
            return; // RKD test

            foreach (DataGridColumn dgcol in dgrdUniversal.Columns)
            {
                try
                {
                    string header = Convert.ToString(dgcol.Header);
                    string propName = dataContext.dictPropertyHeaderDisplayMap.GetKeyFromValue<string, string>(header, false);
                    // dgcol.DisplayIndex = dataContext.dictPropertySortIndex[propName];

                    MessageBoxUtil.Show(true, "Re-arranging column index against SortIndex attribute.", "Functionality pending..");
                }
                catch (Exception ex) { MessageBoxUtil.Show(true, ex.StackTrace, ex.Message); throw; }
            }
        }

        private DataGridColumn UpdateColumnStyle(DataGridColumn dgColCustom, string propName)
        {
            string resourceName = dataContext.dictPropertyCellTemplateMap.GetValueFromKey(propName);
            DataGridTemplateColumn dgColTemplate = new DataGridTemplateColumn();
            DataTemplate dataTemplate = null;

            #region Update templates
            if (!resourceName.IsBlank())
            {
                dataTemplate = (DataTemplate)Resources[resourceName]; // Only complex templates are reqd.
                if (dataTemplate.IsNull())
                    dataTemplate = CreateDefaultTemplate(propName); // Create default template if no resource defined
            }
            else
                dataTemplate = CreateDefaultTemplate(propName);

            // RKD use_chkbx_col_for_bool;

            dgColTemplate.CellTemplate = dataTemplate;
            dgColTemplate.CellEditingTemplate = CreateDefaultEditingTemplate(propName); // editingTemplate; // RKD not reqd. as cells are not editable
            dgColCustom = dgColTemplate;
            #endregion Update cell template

            #region Setting properties
            if (propName == "Description") dgColCustom.MaxWidth = 250;

            dgColCustom.CanUserResize = true;
            dgColCustom.CanUserSort = dataContext.PropertyFieldsSortable._Contains(propName);
            dgColCustom.SortDirection = dgColCustom.CanUserSort ? ListSortDirection.Ascending : dgColCustom.SortDirection;
            dgColCustom.Header = AssignHeader(dgColCustom, propName);
            dgColCustom.DisplayIndex = SetDisplayIndex(propName);
            // dgColCustom.IsFrozen=displayindex<frozencolumncount; // RKD
            dgColCustom.Visibility = Visibility.Visible;
            dgColCustom.IsReadOnly = true;
            #endregion Setting properties

            return dgColCustom;
        }

        private DataTemplate CreateDefaultTemplate(string propName)
        {
            DataTemplate dataTemplate = new DataTemplate();
            if (ExtractColumnDatatype(propName) == typeof(bool))
            {
                FrameworkElementFactory chkFactory = new FrameworkElementFactory(typeof(CheckBox), "chk" + propName);
                chkFactory.SetBinding(CheckBox.IsCheckedProperty, new Binding(propName));
                dataTemplate.VisualTree = chkFactory;
            }
            //else if (ExtractColumnDatatype(propName) == typeof(bool)) // Link
            //{
            //    FrameworkElementFactory chkFactory = new FrameworkElementFactory(typeof(CheckBox), "chk" + propName);
            //    chkFactory.SetBinding(CheckBox.IsCheckedProperty, new Binding(propName));
            //    dataTemplate.VisualTree = chkFactory;
            //}
            else
            {
                FrameworkElementFactory lblFactory = new FrameworkElementFactory(typeof(Label), "lbl" + propName);
                lblFactory.SetBinding(Label.ContentProperty, new Binding(propName));
                dataTemplate.VisualTree = lblFactory;
            }

            return dataTemplate;
        }

        private DataTemplate CreateDefaultEditingTemplate(string propName)
        {
            DataTemplate dataTemplate = new DataTemplate();
            if (ExtractColumnDatatype(propName) != typeof(bool))
            {
                FrameworkElementFactory txtbFactory = new FrameworkElementFactory(typeof(TextBox), "txtb" + propName);
                txtbFactory.SetBinding(TextBox.TextProperty, new Binding(propName));
                dataTemplate.VisualTree = txtbFactory;
            }

            return dataTemplate;
        }

        private Type ExtractColumnDatatype(string propName)
        {
            // RKD - get from attribute; default=templateCol
            return dataContext.displayGroupType.GetProperty(propName).PropertyType;
        }

        private object AssignHeader(DataGridColumn dgColCustom, string propName)
        {
            string headerDisplay = (dgColCustom.CanUserSort ? ": " : "") + dataContext.dictPropertyHeaderDisplayMap[propName];
            string headerDescription = dataContext.dictPropertyDescriptionMap.GetValueFromKey(propName); // tooltip
            headerDescription = (propName == headerDescription) ? headerDisplay : headerDescription;

            return new TextBlock
            {
                Text = headerDisplay,
                ToolTip = headerDescription,
                HorizontalAlignment = HorizontalAlignment.Stretch,
                VerticalAlignment = VerticalAlignment.Center
            };
        }

        private int SetDisplayIndex(string propName)
        {
            int result = -1;
            int current = dataContext.dictPropertySortIndexMap.GetValueFromKey(propName);
            int last = dataContext.dictPropertySortIndexMap.GetValueFromKey(dataContext.nameSortLast);

            if (dataContext.nameSortLast.IsBlank()) // For the first property in order, always set 0
                result = 0;
            else if (current > dataContext.dictColumnsSorted.Values._Max()) // For the property with lower index than sorted at first position
                result = dgrdUniversal.Columns.Count;
            else if (current < dataContext.dictColumnsSorted.Values._Min()) // For the property with higher index than sorted at last position
                result = 0;
            else // For the property to be inserted between
                result = dataContext.dictColumnsSorted.GetValueFromKey(
                    dataContext.dictPropertySortIndexMap.GetKeyFromValue(
                        dataContext.dictPropertySortIndexMap._Where(
                            pr => dataContext.dictColumnsSorted.Keys._Contains(pr.Key) && pr.Value > current)._Select(pr => pr.Value)._Min(), false));

            dataContext.dictColumnsSorted.Add(propName, result);
            dataContext.nameSortLast = propName;
            return result;
        }
    }
}
